home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 2 / Apprentice-Release2.iso / Source Code / Mark Pilgrim / Devil's Cubes 1.0.1 / source / Devil’s Cubes ƒ / MSG Shell ƒ / msg prefs.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-10-30  |  9.8 KB  |  436 lines  |  [TEXT/KAHL]

  1. /**********************************************************************\
  2.  
  3. File:        msg prefs.c
  4.  
  5. Purpose:    This module handles creating/opening/closing/updating
  6.             the preference file, and copying the preference file
  7.             data into application globals (and back).
  8.  
  9.  
  10. Devil’s Cubes -- a simple cubes puzzle
  11. Copyright (C) 1993 Mark Pilgrim
  12.  
  13. This program is free software; you can redistribute it and/or modify
  14. it under the terms of the GNU General Public License as published by
  15. the Free Software Foundation; either version 2 of the License, or
  16. (at your option) any later version.
  17.  
  18. This program is distributed in the hope that it will be useful,
  19. but WITHOUT ANY WARRANTY; without even the implied warranty of
  20. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  21. GNU General Public License for more details.
  22.  
  23. You should have received a copy of the GNU General Public License
  24. along with this program in a file named "GNU General Public License".
  25. If not, write to the Free Software Foundation, 675 Mass Ave,
  26. Cambridge, MA 02139, USA.
  27.  
  28. \**********************************************************************/
  29.  
  30. #include "msg prefs.h"
  31. #include "msg dialogs.h"
  32. #include "msg sounds.h"
  33. #include "msg graphics.h"
  34. #include "msg environment.h"
  35. #include "util.h"
  36. #include "cube files.h"
  37. #include "cube.h"
  38.  
  39. long                gFileID;
  40. Str255                gMyName;
  41. Str255                gMyOrg;
  42. Boolean                gCanSavePrefs;
  43.  
  44. static PrefStruct    thePrefs;
  45. static long            gPrefsFilePos;
  46.  
  47. int PreferencesInit(void)
  48. {
  49.     int            prefsFileID;
  50.     int            err;
  51.     
  52.     gCanSavePrefs=FALSE;
  53.     err=GetFileID();
  54.     if (err!=allsWell)
  55.         return err;
  56.     
  57.     err=OpenPrefsFile(&prefsFileID);
  58.     if (err!=allsWell)
  59.     {
  60.         if ((err==diskReadErr) || (err==diskWriteErr) || (err==virginErr))
  61.             ClosePrefsFile(prefsFileID);
  62.         return err;
  63.     }
  64.     
  65.     err=CheckVersion(prefsFileID);
  66.     if (err!=allsWell)
  67.     {
  68.         ClosePrefsFile(prefsFileID);
  69.         return err;
  70.     }
  71.     
  72.     GetFPos(prefsFileID, &gPrefsFilePos);
  73.     gPrefsFilePos-=sizeof(thePrefs);
  74.     do
  75.     {
  76.         gPrefsFilePos+=sizeof(thePrefs);
  77.         err=GetNextPrefs(prefsFileID);
  78.         if (err==noMorePrefsErr)
  79.             return (Virgin(prefsFileID));
  80.         
  81.         if (err!=allsWell)
  82.         {
  83.             ClosePrefsFile(prefsFileID);
  84.             return err;
  85.         }
  86.         
  87.         err=CheckFileID();
  88.     }
  89.     while (err==IDNotMatchErr);
  90.     
  91.     CopyPrefsToGlobals();
  92.     ClosePrefsFile(prefsFileID);
  93.     
  94.     return allsWell;
  95. }
  96.  
  97. void PrefsError(int err)
  98. {
  99.     switch (err)
  100.     {
  101.         case diskReadErr:
  102.             ParamText("\pThe Devil’s Cubes preferences file could not be accessed, because a \
  103. disk read error occurred.  Default preferences will be used for now, but the file may \
  104. be damaged, and you should probably throw it in the trash.", "\p", "\p", "\p");
  105.             break;
  106.         case diskWriteErr:
  107.             ParamText("\pThe Devil’s Cubes preferences file could not be accessed, because a \
  108. disk write error occurred.  The file may be damaged, and you should probably throw it \
  109. in the trash.","\p","\p","\p");
  110.             break;
  111.         case cantCreatePrefsErr:
  112.             ParamText("\pThe Devil’s Cubes preferences file could not be created.  The \
  113. disk may be locked or full.  Default preferences will be used for now.","\p","\p","\p");
  114.             break;
  115.         case cantOpenPrefsErr:
  116.             ParamText("\pThe Devil’s Cubes preferences file could not be accessed.  The \
  117. file may be damaged, and you should probably throw it in the trash.  Default preferences \
  118. will be used for now.","\p","\p","\p");
  119.             break;
  120.         case versionNotSupportedErr:
  121.             ParamText("\pThe preferences file you have in your system folder was created \
  122. by a later version of Devil’s Cubes than this copy.  If you want to be able to save your \
  123. preferences with this copy, you will have to throw the current preferences file in the \
  124. trash.","\p","\p","\p");
  125.             break;
  126.     }
  127.     switch (err)
  128.     {
  129.         case diskReadErr:
  130.         case diskWriteErr:
  131.         case cantCreatePrefsErr:
  132.         case cantOpenPrefsErr:
  133.         case versionNotSupportedErr:
  134.             gCanSavePrefs=FALSE;
  135.             PositionDialog('ALRT', prefsErrorAlert);
  136.             StopAlert(prefsErrorAlert, 0L);
  137.             break;
  138.         default:
  139.         {
  140.             gCanSavePrefs=TRUE;
  141.             if (err!=virginErr)
  142.                 ShowSplashScreen();
  143.         }
  144.     }
  145. }
  146.  
  147. int OpenPrefsFile(int *prefsFileID)
  148. {
  149.     int                thisFile;
  150.     OSErr            isHuman;
  151.     int                vRefNum;
  152.     long            dirID;
  153.     FSSpec            prefsFile;
  154.     FInfo            prefsInfo;
  155.     Boolean            newPrefs;
  156.     unsigned char    *name=PREFS_FILE_NAME;
  157.     
  158.     newPrefs=FALSE;
  159.     isHuman=FindFolder(kOnSystemDisk, 'pref', kCreateFolder, &vRefNum, &dirID);
  160.     
  161.     if (isHuman!=noErr)
  162.         return cantOpenPrefsErr;
  163.     if (gHasFSSpecs)
  164.     {
  165.         isHuman=FSMakeFSSpec(vRefNum, dirID, name, &prefsFile);
  166.         if (isHuman!=noErr)
  167.         {
  168.             if (isHuman==fnfErr)
  169.             {
  170.                 isHuman=FSpCreate(&prefsFile, CREATOR, PREFS_TYPE, 0);
  171.                 if (isHuman!=noErr)
  172.                     return cantCreatePrefsErr;
  173.                 newPrefs=TRUE;
  174.             }
  175.             else return cantOpenPrefsErr;
  176.         }
  177.         isHuman=FSpOpenDF(&prefsFile, fsRdWrPerm, &thisFile);
  178.         *prefsFileID=thisFile;
  179.         if (isHuman!=noErr)
  180.             return cantOpenPrefsErr;
  181.     }
  182.     else
  183.     {
  184.         isHuman=HOpen(vRefNum, dirID, name, fsRdWrPerm, &thisFile);
  185.         *prefsFileID=thisFile;
  186.         if (isHuman!=noErr)
  187.         {
  188.             if (isHuman==fnfErr)
  189.             {
  190.                 isHuman=HCreate(vRefNum, dirID, name, CREATOR, PREFS_TYPE);
  191.                 if (isHuman!=noErr)
  192.                     return cantCreatePrefsErr;
  193.                 prefsInfo.fdType=PREFS_TYPE;
  194.                 prefsInfo.fdCreator=CREATOR;
  195.                 prefsInfo.fdFlags=0;
  196.                 prefsInfo.fdLocation.h=prefsInfo.fdLocation.v=0;
  197.                 prefsInfo.fdFldr=0;
  198.                 isHuman=HSetFInfo(vRefNum, dirID, name, &prefsInfo);
  199.                 if (isHuman!=noErr)
  200.                     return cantCreatePrefsErr;
  201.                 isHuman=HOpen(vRefNum, dirID, name, fsRdWrPerm, &thisFile);
  202.                 *prefsFileID=thisFile;
  203.                 if (isHuman!=noErr)
  204.                     return cantOpenPrefsErr;
  205.                 newPrefs=TRUE;
  206.             }
  207.             else return cantOpenPrefsErr;
  208.         }
  209.     }
  210.     if (newPrefs)
  211.         return SetupNewPrefsFile(*prefsFileID);
  212.     
  213.     return allsWell;
  214. }
  215.  
  216. int SetupNewPrefsFile(int prefsFileID)
  217. {
  218.     int                err;
  219.     OSErr            isHuman;
  220.     long            count;
  221.     int                temp;
  222.     
  223.     gPrefsFilePos=2L;
  224.     isHuman=SetEOF(prefsFileID, 2L);
  225.     if (isHuman!=noErr)
  226.         return diskWriteErr;
  227.     SetFPos(prefsFileID, 1, 0L);
  228.     temp=PREFS_HEADER_VERSION;
  229.     count=2L;
  230.     isHuman=FSWrite(prefsFileID, &count, &temp);
  231.     if (isHuman!=noErr)
  232.         return diskWriteErr;        
  233.     err=Virgin(prefsFileID);
  234.     return err;
  235. }
  236.  
  237. void ClosePrefsFile(int prefsFileID)
  238. {
  239.     FSClose(prefsFileID);
  240.     FlushVol(0L, kOnSystemDisk);
  241. }
  242.  
  243. int GetNextPrefs(int prefsFileID)
  244. {
  245.     OSErr        isHuman;
  246.     long        count;
  247.     
  248.     count=sizeof(thePrefs);
  249.     isHuman=FSRead(prefsFileID, &count, &thePrefs);
  250.     if (isHuman==eofErr)
  251.         return noMorePrefsErr;
  252.     if (isHuman!=noErr)
  253.         return diskReadErr;
  254.     
  255.     return allsWell;
  256. }
  257.  
  258. int SavePrefs(int prefsFileID)
  259. {
  260.     long        oldEOF;
  261.     OSErr        isHuman;
  262.     long        count;
  263.     
  264.     GetEOF(prefsFileID, &oldEOF);
  265.     if (gPrefsFilePos>=oldEOF)
  266.     {
  267.         isHuman=SetEOF(prefsFileID, oldEOF+sizeof(thePrefs));
  268.         if (isHuman!=noErr)
  269.             return diskWriteErr;
  270.     }
  271.     SetFPos(prefsFileID, 1, gPrefsFilePos);
  272.     count=sizeof(thePrefs);
  273.     isHuman=FSWrite(prefsFileID, &count, &thePrefs);
  274.     if (isHuman!=noErr)
  275.         return diskWriteErr;
  276.     
  277.     return allsWell;
  278. }
  279.  
  280. int CheckVersion(int prefsFileID)
  281. {
  282.     OSErr        isHuman;
  283.     long        count;
  284.     int            temp;
  285.     
  286.     count=2L;
  287.     isHuman=FSRead(prefsFileID, &count, &temp);
  288.     if (isHuman!=noErr)
  289.         return diskReadErr;
  290.     if (temp>PREFS_HEADER_VERSION)
  291.         return versionNotSupportedErr;
  292.     if (temp<PREFS_HEADER_VERSION)
  293.         return SetupNewPrefsFile(prefsFileID);
  294.     
  295.     return allsWell;
  296. }
  297.  
  298. int GetFileID(void)
  299. {
  300.     CInfoPBRec        pb;
  301.     int                err;
  302.     
  303.     pb.hFileInfo.ioCompletion=0L;
  304.     pb.hFileInfo.ioNamePtr=CurApName;
  305.     pb.hFileInfo.ioVRefNum=0;
  306.     pb.hFileInfo.ioFDirIndex=0;
  307.     pb.hFileInfo.ioDirID=0;
  308.     err=PBGetCatInfo(&pb, FALSE);
  309.     if (err!=noErr)
  310.         return diskReadErr;
  311.     
  312.     gFileID=pb.hFileInfo.ioDirID;
  313.     
  314.     return allsWell;
  315. }
  316.  
  317. int CheckFileID(void)
  318. {
  319.     return (thePrefs.fileID==gFileID) ? allsWell : IDNotMatchErr;
  320. }
  321.  
  322. int Virgin(int prefsFileID)
  323. {
  324.     int            err;
  325.     
  326.     DefaultPrefs();
  327.     CopyGlobalsToPrefs();
  328.     err=SavePrefs(prefsFileID);
  329.     if (err!=allsWell)
  330.         return err;
  331.     DoSound(sound_virgin);
  332.     GetRegistration();
  333.     CopyGlobalsToPrefs();
  334.     err=SavePrefs(prefsFileID);
  335.     
  336.     return (err==allsWell) ? virginErr : err;
  337. }
  338.  
  339. void DefaultPrefs(void)
  340. {
  341.     gMyName[0]=0x03;
  342.     gMyName[1]='B';
  343.     gMyName[2]='o';
  344.     gMyName[3]='b';
  345.     gMyOrg[0]=0x00;
  346.     gSoundToggle=0xFF;
  347.     gUseMirror=0xFF;
  348.     gShowAll=0xFF;
  349. }
  350.  
  351. void CopyGlobalsToPrefs(void)
  352. {
  353.     Mymemset(&thePrefs, 0, sizeof(thePrefs));
  354.     if (gMyName[0]>0x27)
  355.         gMyName[0]=0x27;
  356.     if (gMyOrg[0]>0x27)
  357.         gMyOrg[0]=0x27;
  358.     Mymemcpy(thePrefs.regname, gMyName, gMyName[0]+1);
  359.     Mymemcpy(thePrefs.regorg, gMyOrg, gMyOrg[0]+1);
  360.     thePrefs.sound=gSoundToggle;
  361.     thePrefs.usemirror=gUseMirror;
  362.     thePrefs.showall=gShowAll;
  363.     thePrefs.unused=0x00;
  364.     thePrefs.fileID=gFileID;
  365. }
  366.  
  367. void CopyPrefsToGlobals(void)
  368. {
  369.     Mymemcpy(gMyName, thePrefs.regname, thePrefs.regname[0]+1);
  370.     Mymemcpy(gMyOrg, thePrefs.regorg, thePrefs.regorg[0]+1);
  371.     gSoundToggle=thePrefs.sound;
  372.     gUseMirror=thePrefs.usemirror;
  373.     gShowAll=thePrefs.showall;
  374. }
  375.  
  376. void GetRegistration(void)
  377. {
  378.     DialogPtr        theDlog;
  379.     int                itemSelected = 0;
  380.     int                newleft;
  381.     int                newtop;
  382.     int                itemType;
  383.     Handle            item;
  384.     Rect            box;
  385.     int                dlogID;
  386.     
  387.     if(GetWindowDepth() == 1)
  388.         dlogID = bwPersonalDialog;
  389.     else
  390.         dlogID = colorPersonalDialog;
  391.         
  392.     theDlog = GetNewDialog(dlogID, 0L, (WindowPtr)-1L);
  393.     newleft = gMainScreenBounds.left + (((gMainScreenBounds.right -
  394.                 gMainScreenBounds.left) - (theDlog->portRect.right -
  395.                 theDlog->portRect.left)) / 2);
  396.     newtop = gMainScreenBounds.top + (((gMainScreenBounds.bottom -
  397.                 gMainScreenBounds.top) - (theDlog->portRect.bottom -
  398.                 theDlog->portRect.top)) / 2);
  399.     if(newtop < 15)
  400.         newtop = 15;
  401.     GetDItem(theDlog, 1, &itemType, &item, &box);
  402.     InsetRect(&box, -4, -4);
  403.     SetDItem(theDlog, 8, userItem, OutlineDefaultButton, &box);
  404.  
  405.     MoveWindow(theDlog, newleft, newtop, TRUE);
  406.     ShowWindow(theDlog);
  407.     while(itemSelected != 1)
  408.     {
  409.         ModalDialog(0L, &itemSelected);
  410.     }
  411.     GetDItem(theDlog,4,&itemType,&item,&box);
  412.     GetIText(item,&gMyName);
  413.     
  414.     GetDItem(theDlog,5,&itemType,&item,&box);
  415.     GetIText(item,&gMyOrg);
  416.  
  417.     if (gMyName[0]=='\0')
  418.         DefaultPrefs();
  419.  
  420.     HideWindow(theDlog);
  421.     DisposeDialog(theDlog);
  422. }
  423.  
  424. void SaveThePrefs(void)
  425. {
  426.     int            prefsFileID;
  427.     
  428.     if (gCanSavePrefs)
  429.     {
  430.         OpenPrefsFile(&prefsFileID);
  431.         CopyGlobalsToPrefs();
  432.         SavePrefs(prefsFileID);
  433.         ClosePrefsFile(prefsFileID);
  434.     }
  435. }
  436.